home *** CD-ROM | disk | FTP | other *** search
/ Gekkan Dennou Club 147 / Gekkan Dennou Club - 2000.8 Vol. 147 (Japan).7z / Gekkan Dennou Club - 2000.8 Vol. 147 (Japan) (Track 1).bin / docs / ippon / ver / 013 / eshot.c < prev    next >
C/C++ Source or Header  |  2000-07-07  |  3KB  |  117 lines

  1. /* eshot.c */
  2.  
  3. #include <stdio.h>
  4. #include <xsp2lib.h>
  5.  
  6. #include "main.h"
  7. #include "player.h"
  8. #include "eshot.h"
  9.  
  10. #define    PALET_ESHOT    0x0300
  11.  
  12. #define ESHOT_MAX    200    /* 敵弾最大数 */
  13. static ESHOT eshot[ESHOT_MAX];    /* ワーク */
  14.  
  15.  
  16.  
  17. /* ゲーム開始時に呼ばれる */
  18. void EshotInit (void)
  19. {
  20.     int i;
  21.  
  22.     /* リストをつなげる */
  23.     eshot_top = NULL;
  24.     eshot_null_top = eshot;
  25.     for (i = 0; i < ESHOT_MAX; i++)
  26.         eshot[i].next = &eshot[i + 1];
  27.  
  28.     eshot[ESHOT_MAX - 1].next = NULL;
  29. }
  30.  
  31.  
  32.  
  33. /* 敵弾出現時に呼ばれる */
  34. void EshotAlloc (short type, signed short x, signed short y, unsigned char speed, unsigned char angle)
  35. {
  36.     ESHOT *p;
  37.  
  38.     if (eshot_null_top == NULL)    /* ワークの空きはあるか? */
  39.         return;
  40.  
  41.     p = eshot_null_top;
  42.     eshot_null_top = p->next;
  43.     p->next = eshot_top;
  44.     eshot_top = p;
  45.  
  46.     p->lx = (x - 8) << 16;    /* (8,8) がスプライト座標の中心なので補正 */
  47.     p->ly = (y - 8) << 16;
  48.     p->vx = xytable[speed][angle].x;
  49.     p->vy = xytable[speed][angle].y;
  50.  
  51.     p->hit_p = 3;        /* 速度を 3.0 未満にする事 */
  52.     p->pt = sp_eshot + 1;
  53.     p->info = PALET_ESHOT | PRIORITY_ESHOT;
  54. }
  55.  
  56.  
  57.  
  58. /* 垂直同期ごとに呼ばれる */
  59. void EshotMove (void)
  60. {
  61.     ESHOT *p, *q;
  62.     signed short pl_x = player->x - 8, pl_y = player->y - 8;
  63.  
  64. #ifdef DEBUG
  65.     eshot_sum = 0;
  66. #endif
  67.     p = eshot_top;        /* 現在注目しているワーク */
  68.     q = NULL;        /* 1つ前のワーク(ワーク削除時に必要) */
  69.  
  70.     while (p != NULL) {
  71.         signed short p_x, p_y;
  72.  
  73. #ifdef DEBUG
  74.         eshot_sum++;
  75. #endif
  76.         /* 速度を足して上位ワード(固定整数部)だけ取り出す */
  77.         p_x = p->x = (p->lx += p->vx) >> 16;
  78.         p_y = p->y = (p->ly += p->vy) >> 16;
  79.  
  80.         /* 敵弾が画面外に出たか? */
  81.         /* (画面右から出た判定と左から出た判定を1回の比較で行っている) */
  82.         if (((unsigned short) p_x > 256 + 16) || ((unsigned short) p_y > 256 + 16)) {
  83.             /* 敵弾が画面外へ出たので消去 */
  84.             if (q == NULL) {    /* リストの一番最初を削除 */
  85.                 eshot_top = p->next;
  86.                 p->next = eshot_null_top;
  87.                 eshot_null_top = p;
  88.                 q = NULL;
  89.                 p = eshot_top;
  90.             } else {
  91.                 q->next = p->next;
  92.                 p->next = eshot_null_top;
  93.                 eshot_null_top = p;
  94.                 p = q->next;
  95.             }
  96.         } else {
  97.             /* 画面外へ出ていない時 */
  98.  
  99.             /* 敵弾と自機の当たり判定 */
  100.             /* この辺の最適化は -fstrings-reduce が頑張ってくれるハズ */
  101.             signed short t, t2 = p->hit_p;
  102.             if (((t = p_y - t2) <= pl_y)
  103.                 && ((t += (short) (t2 << 1)) >= pl_y)
  104.                 && ((t = p_x + t2) >= pl_x)
  105.                 && ((t -= (short) (t2 << 1)) <= pl_x)) {
  106.                 if (player->status == PLAYER_STATUS_ALIVE)
  107.                     player->status = PLAYER_STATUS_DEAD;
  108.             } else {
  109.                 xsp_set_st (p);
  110.             }
  111.  
  112.             q = p;
  113.             p = p->next;
  114.         }
  115.     }
  116. }
  117.